package cn.lystudio.rohmtimeopwide_background_v11.service.impl;

import cn.dev33.satoken.stp.StpUtil;
import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.convert.Convert;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.lystudio.rohmtimeopwide_background_v11.entity.dto.MachineDTO;
import cn.lystudio.rohmtimeopwide_background_v11.entity.po.DepartmentsPO;
import cn.lystudio.rohmtimeopwide_background_v11.entity.po.MachinePO;
import cn.lystudio.rohmtimeopwide_background_v11.exceptions.JsonException;
import cn.lystudio.rohmtimeopwide_background_v11.mapper.DepartmentsPOMapper;
import cn.lystudio.rohmtimeopwide_background_v11.mapper.MachinePOMapper;
import cn.lystudio.rohmtimeopwide_background_v11.service.MachineService;
import com.baomidou.dynamic.datasource.annotation.DS;
import com.baomidou.dynamic.datasource.annotation.DSTransactional;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.List;

@Service
@DS("master")

public class MachineServiceImpl implements MachineService {
    @Resource
    private MachinePOMapper machinePOMapper;
    @Resource
    private DepartmentsPOMapper departmentsPOMapper;

    /**
     * 鉴权,获取所有设备信息
     *
     * @param machineNo 搜索选项
     * @return
     */
    @Override
    public List<MachineDTO> getAll(String machineNo) {
        // 1.获取制造部权限
        List<String> topDeptPermisList = StpUtil.getPermissionList(StpUtil.getLoginIdAsString());
        if (topDeptPermisList.size() != 1) return null;
        LambdaQueryWrapper<DepartmentsPO> wrapper = new QueryWrapper<DepartmentsPO>().lambda();
        wrapper.eq(DepartmentsPO::getEnabled, true)
                .eq(DepartmentsPO::getParentID, 0)
                .ge(DepartmentsPO::getDepartmentID, 10)
                // 非超级管理员
                .eq(Convert.toInt(topDeptPermisList.get(0)) >= 10, DepartmentsPO::getDepartmentID, topDeptPermisList.get(0));
        List<DepartmentsPO> topDeptList = departmentsPOMapper.selectList(wrapper);
        if (CollUtil.isEmpty(topDeptList)) return null;
        // 1.1 将制造部权限转换成ID List
        List<Integer> topDeptIDList = CollUtil.list(false);
        CollUtil.forEach(topDeptList.iterator(), (topDept, index) -> {
            topDeptIDList.add(topDept.getDepartmentID());
        });

        // 2. 通过制造部权限ID List,筛选出可以使用的制造工程List
        LambdaQueryWrapper<DepartmentsPO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.in(DepartmentsPO::getParentID, topDeptIDList)
                .eq(DepartmentsPO::getEnabled, true)
                .ne(DepartmentsPO::getParentID, 0)
                .ge(DepartmentsPO::getDepartmentID, 10);
        List<DepartmentsPO> secDeptList = departmentsPOMapper.selectList(wrapper1);
        if (CollUtil.isEmpty(secDeptList)) return null;
        //2.1 将可以使用的制造工程LIST转换成 ID List
        List<Integer> secDeptIDList = CollUtil.list(false);
        CollUtil.forEach(secDeptList.iterator(), (secDept, index) -> {
            secDeptIDList.add(secDept.getDepartmentID());
        });

        // 5.查询功能
        List<Integer> machineSearchedIDList = CollUtil.list(false);
        if (StrUtil.isNotEmpty(machineNo)) {
            LambdaQueryWrapper<MachinePO> wrapper3 = new LambdaQueryWrapper<>();
            wrapper3.like(MachinePO::getMachineNo, machineNo);
            List<MachinePO> machineSearchedList = machinePOMapper.selectList(wrapper3);
            CollUtil.forEach(machineSearchedList.iterator(), (machine, index) -> {
                machineSearchedIDList.add(machine.getMachineID());
            });
        }
        if (StrUtil.isNotEmpty(machineNo) && CollUtil.isEmpty(machineSearchedIDList)) return null;


        //3.通过制造工程ID List 获取设备权限
        LambdaQueryWrapper<MachinePO> wrapper2 = new LambdaQueryWrapper<>();
        wrapper2.in(MachinePO::getSecDeptID, secDeptIDList)
                .in(StrUtil.isNotEmpty(machineNo), MachinePO::getMachineID, machineSearchedIDList)
                .orderByAsc(MachinePO::getMachineNo);
        List<MachinePO> machinePOList = machinePOMapper.selectList(wrapper2);
        if (CollUtil.isEmpty(machinePOList)) return null;

        //4.获取machineDTO
        List<MachineDTO> machineDTOList = CollUtil.list(false);
        CollUtil.forEach(machinePOList.iterator(), (machine, index) -> {
            MachineDTO machineDTO = new MachineDTO();
            machineDTO.setMachine(machine);
            machineDTO.setSecDept(CollUtil.findOne(secDeptList, secDept -> {
                        return secDept.getDepartmentID().equals(machine.getSecDeptID());
                    })
            );
            machineDTOList.add(machineDTO);
        });
        //4.1 过滤无用数据
        CollUtil.filter(machineDTOList, machineDTO -> {
            return (ObjectUtil.isNotEmpty(machineDTO.getMachine()) && ObjectUtil.isNotEmpty(machineDTO.getSecDept()));
        });
        // 5.返回数据
        return machineDTOList;
    }

    @Override
    public int uptMachineEnabled(Integer machineID, Boolean enabled) {
        MachinePO machinePO = new MachinePO();
        machinePO.setMachineID(machineID);
        machinePO.setEnabled(enabled);
        return machinePOMapper.updateById(machinePO);
    }

    @Override
    @DSTransactional
    public int delMachine(Integer machineID) {
        return machinePOMapper.deleteById(machineID);
    }

    @Override
    @DSTransactional
    public int addMachine(MachinePO machine) {

        int res1 = 0;
        MachinePO machinePO = machinePOMapper.get1NoCondition(machine);
        if (ObjectUtil.isEmpty(machinePO)) {
            res1 = machinePOMapper.insert(machine);
        } else {
            machine.setEnabled(true);
            machine.setDeleted(false);
            res1 = machinePOMapper.uptMachineNoCondition(machine);
        }
        if (res1 < 1 ) throw new JsonException(500, "添加失败");
        return 1;
    }

    @Override
    @DSTransactional
    public int uptMachine(MachinePO machine) {
        return machinePOMapper.updateById(machine);
    }

    /**
     * 通过制造工程ID获取其下的所有设备
     * @param secDeptID
     * @return
     */
    @Override
    public List<MachinePO> getMachineListBySecDeptID(Integer secDeptID) {
        LambdaQueryWrapper<MachinePO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MachinePO::getSecDeptID,secDeptID);
        return machinePOMapper.selectList(wrapper);
    }

    @Override
    public MachinePO getMachineByMachineNo(String machineNo) {
        return machinePOMapper.selectOne(new LambdaQueryWrapper<MachinePO>().eq(MachinePO::getMachineNo,machineNo).last("limit 1"));
    }

    @Override
    public MachinePO get1ByMachineNo_Usable(String machineNo) {
        return machinePOMapper.get1ByMachineNo_Usable(machineNo);
    }

    @Override
    public MachinePO getMachine4SSD1BT(String machineNo) {
        LambdaQueryWrapper<MachinePO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MachinePO::getMachineNo,machineNo)
                .eq(MachinePO::getEnabled,true)
                .last("LIMIT 1");
        MachinePO machinePO = machinePOMapper.selectOne(wrapper);
        if(ObjectUtil.isEmpty(machinePO)) return null;
        LambdaQueryWrapper<DepartmentsPO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.eq(DepartmentsPO::getParentID,146)
                .eq(DepartmentsPO::getDepartmentID,machinePO.getSecDeptID());
        List<DepartmentsPO> departmentsPOList = departmentsPOMapper.selectList(wrapper1);
        if(CollUtil.isEmpty(departmentsPOList)) return null;
        return machinePO;
    }

    @Override
    public MachinePO getMachine4SSD1ZL(String machineNo) {
        LambdaQueryWrapper<MachinePO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MachinePO::getMachineNo,machineNo)
                .eq(MachinePO::getEnabled,true)
                .last("LIMIT 1");
        MachinePO machinePO = machinePOMapper.selectOne(wrapper);
        if(ObjectUtil.isEmpty(machinePO)) return null;

        LambdaQueryWrapper<DepartmentsPO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.eq(DepartmentsPO::getParentID,144)
                .eq(DepartmentsPO::getDepartmentID,machinePO.getSecDeptID());
        List<DepartmentsPO> departmentsPOList = departmentsPOMapper.selectList(wrapper1);
        if(CollUtil.isEmpty(departmentsPOList)) return null;
        return machinePO;
    }

    @Override
    public MachinePO getMachine4SSD1CD(String machineNo) {
        LambdaQueryWrapper<MachinePO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MachinePO::getMachineNo,machineNo)
                .eq(MachinePO::getEnabled,true)
                .last("LIMIT 1");
        MachinePO machinePO = machinePOMapper.selectOne(wrapper);
        if(ObjectUtil.isEmpty(machinePO)) return null;

        LambdaQueryWrapper<DepartmentsPO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.eq(DepartmentsPO::getParentID,147)
                .eq(DepartmentsPO::getDepartmentID,machinePO.getSecDeptID());
        List<DepartmentsPO> departmentsPOList = departmentsPOMapper.selectList(wrapper1);
        if(CollUtil.isEmpty(departmentsPOList)) return null;
        return machinePO;
    }

    @Override
    public List<MachinePO> getUSMZuLiMachineList() {
        LambdaQueryWrapper<DepartmentsPO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(DepartmentsPO::getParentID,144)
                .eq(DepartmentsPO::getEnabled,true);
        List<DepartmentsPO> departmentsPOList = departmentsPOMapper.selectList(wrapper);
        if(CollUtil.isEmpty(departmentsPOList)) return null;
        List<Integer> secDeptIDList = CollUtil.list(false);
        CollUtil.forEach(departmentsPOList.iterator(),(department,index)->{
            secDeptIDList.add(department.getDepartmentID());
        });

        LambdaQueryWrapper<MachinePO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.in(MachinePO::getSecDeptID,secDeptIDList)
                .eq(MachinePO::getEnabled,true);

        return machinePOMapper.selectList(wrapper1);
    }

    @Override
    public List<MachinePO> getUSMBtMachineList() {
        LambdaQueryWrapper<DepartmentsPO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(DepartmentsPO::getParentID,146)
                .eq(DepartmentsPO::getEnabled,true);
        List<DepartmentsPO> departmentsPOList = departmentsPOMapper.selectList(wrapper);
        if(CollUtil.isEmpty(departmentsPOList)) return null;
        List<Integer> secDeptIDList = CollUtil.list(false);
        CollUtil.forEach(departmentsPOList.iterator(),(department,index)->{
            secDeptIDList.add(department.getDepartmentID());
        });

        LambdaQueryWrapper<MachinePO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.in(MachinePO::getSecDeptID,secDeptIDList)
                .eq(MachinePO::getEnabled,true);

        return machinePOMapper.selectList(wrapper1);
    }

    @Override
    public MachineDTO getMachineDTOByMachineNo(String machineNo) {
        // 1.根据设备号,查找设备
        LambdaQueryWrapper<MachinePO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MachinePO::getMachineNo,machineNo)
            .eq(MachinePO::getEnabled,true)
            .last("LIMIT 1");
        MachinePO machinePO = machinePOMapper.selectOne(wrapper);
        if(ObjectUtil.isEmpty(machinePO)) return null;
        // 2.根据设备信息,查找部门信息
        LambdaQueryWrapper<DepartmentsPO> wrapper1 = new LambdaQueryWrapper<>();
        wrapper1.eq(DepartmentsPO::getDepartmentID,machinePO.getSecDeptID())
            .eq(DepartmentsPO::getEnabled,true)
            .last("LIMIT 1");
        DepartmentsPO secDeptPO = departmentsPOMapper.selectOne(wrapper1);
        if(ObjectUtil.isEmpty(secDeptPO)) return null;
        // 3.根据部门信息,查制造部信息
        LambdaQueryWrapper<DepartmentsPO> wrapper2 = new LambdaQueryWrapper<>();
        wrapper2.eq(DepartmentsPO::getDepartmentID,secDeptPO.getParentID())
            .eq(DepartmentsPO::getEnabled,true)
            .last("LIMIT 1");
        DepartmentsPO topDeptPO = departmentsPOMapper.selectOne(wrapper2);
        if(ObjectUtil.isEmpty(topDeptPO)) return null;

        // 4.组装DTO
        MachineDTO machineDTO = new MachineDTO();
        machineDTO.setMachine(machinePO);
        machineDTO.setSecDept(secDeptPO);
        return machineDTO;
    }

    @Override
    public List<MachinePO> getMachineListBySecDeptID_machineTYpe(Integer secDeptID, Integer machineType) {
        LambdaQueryWrapper<MachinePO> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(MachinePO::getSecDeptID,secDeptID)
            .eq(MachinePO::getMachineType,machineType);
        return machinePOMapper.selectList(wrapper);
    }


}
